package com.laijiale.component;

import cn.hutool.core.util.ObjectUtil;
import lombok.SneakyThrows;
import org.aspectj.lang.ProceedingJoinPoint;
import org.aspectj.lang.annotation.Around;
import org.aspectj.lang.annotation.Aspect;
import org.springframework.stereotype.Component;

import java.util.Arrays;

@Aspect
@Component
public class ServiceAspect {
    @Around("execution(public * com.laijiale.service.*.*(..))")
    @SneakyThrows
    public Object aroundAdvice(ProceedingJoinPoint pjp){

        // 获取方法参数
        Object[] args = pjp.getArgs();
        // 组装完整业务方法名：类名.方法名()
        String className = pjp.getTarget().toString();
        className = className.substring(className.lastIndexOf('.') + 1, className.indexOf('@'));
        String methodName = pjp.getSignature().getName();
        methodName = className + "." + methodName + "()";

        // 前置通知: 检查参数中是否存在空值
        if (ObjectUtil.hasNull(args)) {
            throw new RuntimeException("通知: 业务方法 " + methodName + "中存在null值参数");
        }

        // 调用目标方法
        Object returnValue = pjp.proceed(args);

        // 后置通知: 记录业务层调用日志
        System.out.printf("通知: 业务方法 %s 被调用:\n\t形参：%s\n\t返回：%s\n",
                methodName, Arrays.toString(args), returnValue);

        // 返回目标方法的返回值
        return returnValue;

    }
}
